home *** CD-ROM | disk | FTP | other *** search
- /*
- File: BigEasyControls.c
-
- Copyright: © 1990-1991, 1994 by Apple Computer, Inc., all rights reserved.
-
- This file is used in these builds: Warhol
-
- Change History (most recent first):
-
- <9> 6/10/94 dvb nil control list behaves better.
- <8> 4/13/92 dvb Minor bugs (empty controllist, &c)
- <7> 4/3/92 dvb New calls.
- <6> 5/28/91 JB Added prototypes for BigEasy Proc Ptrs
- <5> 5/22/91 PH new style prototypes
- <4> 4/25/91 JB Changing to new THINK_C interface files
- <3> 12/5/90 GW Fix dispose easycontrol
- <2> 11/17/90 dvb Return unprocessed key-actions
- <1> 11/17/90 dvb New again after 1st CD!
-
- To Do:
- */
-
- /*
- * file: BigEasyControls.c
- *
- * started 25 May 1990 12:07:24 Friday at 310 Nobel
- *
- * david van brink
- *
- */
-
- /************************************
- * Inclusions
- ************************************/
-
- #include <Memory.h>
- #include <QuickDraw.h>
- #include <Events.h>
-
- #define privateEasyControls
- #include "BigEasy2.h"
- #include "BigEasyGrafish.h"
- #include "BigEasyTextish.h"
- #include "BigEasyControls.h"
-
-
- /************************************
- * Globals
- ************************************/
-
- static short defaultColors[6] =
- {
- 0,
- PackColor555(46035,46035,46035),
- PackColor555(25535,65535,25535),
- PackColor555(24000,0,0),
- 0,
- 0
- };
-
- /************************************
- * Prototypes
- ************************************/
- static void SelectEasyControl(easyControl ech, easyControlList list);
- static void UnhighlightSelection(easyControlList list);
- static void WalkDrawEasyControlList(easyControlList list,long,long);
- static void WalkInvalEasyControlList(easyControlList list,long,long);
- static short GetControlNumber(easyControl ech);
-
- /************************************
- * Routines
- ************************************/
- easyControl NewEasyControl(easyControlType *type,Rect *r, long variation, void *style,
- long refcon,long id,long value,easyControlList list)
- /*
- * Make a new handle for an easy control, and call the
- * init routine for that control. Then, add it to the
- * list passed in.
- */
- {
- easyControl ech;
- register easyControlPtr ec;
- register easyControl w;
- easyControlListPtr l;
-
- ech = (easyControl)NewHandle(sizeof(easyControlRecord));
- FailNil(ech);
-
- HLock((Handle)ech);
- ec = *ech;
-
- ec->next = nil;
- ec->list = list;
- l = *list;
- w = l->firstControl;
- if(!w)
- {
- ec->prev = nil;
- l->firstControl = ech;
- }
- else
- {
- while((**w).next)
- w = (**w).next;
- (**w).next = ech;
- ec->prev = w;
- }
-
- ec->type = type;
- ec->rect = *r;
- ec->flags = easyControlActive;
- ec->refcon = refcon;
- ec->id = id;
- ec->variation = variation;
- ec->value = value;
- ec->style = style;
- ec->state = nil;
-
- ec->color[0] = defaultColors[0];
- ec->color[1] = defaultColors[1];
- ec->color[2] = defaultColors[2];
- ec->color[3] = defaultColors[3];
- ec->color[4] = defaultColors[4];
- ec->color[5] = defaultColors[5];
-
- ec->actionProc = nil;
- ec->initActionProc = nil;
- ec->doneActionProc = nil;
- ec->valueProc = nil;
- /* ec->keyProc = nil; */
-
- ec->low = 0;
- ec->high = 100;
-
- TextFont((**list).textFont);
- TextFace((**list).textFace);
- TextSize((**list).textSize);
-
-
- (*type->newProc)(ec);
-
- HUnlock((Handle)ech);
- return ech;
- }
-
- void DisposeEasyControl(easyControl ech, easyControlList list)
- /*
- * remove a control from the list passed
- */
- {
- register easyControl *w;
- register easyControlPtr ec;
- register easyControlListPtr l;
- easyControl last;
-
- l = *list;
- last = nil;
- ec = *ech;
- w = &l->firstControl;
-
- while(*w)
- {
- if(*w == ech)
- {
- *w = ec->next;
- if (*w != nil) /* Make sure its not nil - GW */
- (**(ec->next)).prev = last;
- goto goHome;
- }
- else
- {
- last = *w;
- w = &(***w).next;
- }
- }
- goHome:;
- DisposHandle((Handle)ech);
- }
-
- void DisposeEasyControlList(easyControlList list)
- {
- register easyControl w,n;
-
- w = (**list).firstControl;
- while(w)
- {
- n = (**w).next;
- DisposeEasyControl(w,list);
- w = n;
- }
- DisposHandle((Handle)list);
- }
-
- easyControlList NewEasyControlList(WindowPtr w,long refcon)
- {
- easyControlList listH;
- easyControlListPtr list;
-
- listH = (easyControlList)NewHandle(sizeof(easyControlListRecord));
- list = *listH;
- list->firstControl = nil;
- list->selectedControl = nil;
- list->nextSelectedControl = nil;
- list->ownerWindow = w;
- list->refcon = refcon;
- list->textFont = 3; /* geneva */
- list->textSize = 9;
- list->textFace = bold;
- list->nextIdle = 0;
- list->ticksPerIdle = 30;
-
- return listH;
- }
-
- void KeyEasyControlList(easyControlList listH,short key,short mods,controlClickResult *ccr)
- /*
- * Pass a keypress to the currently
- * selected control. we swipe "tab"s
- * to skip from control to control, and
- * "esc" to say "no control selected".
- */
- {
- register easyControl ech;
- register easyControlPtr ec;
- register easyControlListPtr list;
- short listHState;
- Boolean tookKey;
-
- listHState = HGetState((Handle)listH);
- HLock((Handle)listH);
- list = *listH;
-
- if(ccr)
- {
- ccr->whichControl = nil;
- ccr->tracked = false;
- ccr->value = 0;
- ccr->refcon = 0;
- ccr->id = 0;
- }
-
- ech = list->selectedControl;
- if(key == '\t')
- {
- nextEch:
- if(ech)
- {
- if(mods & shiftKey)
- ech = (**ech).prev;
- else
- ech =(**ech).next;
- }
- else
- {
- ech = list->firstControl;
- if(mods & shiftKey && ech)
- while((**ech).next)
- ech = (**ech).next;
- }
- if(list->nextSelectedControl)
- {
- ech = list->nextSelectedControl;
- list->nextSelectedControl = nil;
- }
-
- if(ech && !(**ech).type->keyProc) /* if its got no keyproc, it doesn't do keypresses */
- goto nextEch;
- SelectEasyControl(ech,listH);
- }
- else if(key == 27) /* the escape key */
- {
- SelectEasyControl(nil,listH);
- list->nextSelectedControl = ech;
- }
- else
- {
- if(ech)
- {
- HLock((Handle)ech);
- ec = *ech;
- (*ec->type->keyProc)(ec,key,mods,&tookKey);
-
- if(ccr)
- {
- ccr->whichControl = ech;
- ccr->tracked = tookKey;
- ccr->value = ec->value;
- ccr->refcon = ec->refcon;
- ccr->id = ec->id;
- }
-
- HUnlock((Handle)ech);
-
- UnhighlightSelection(listH); /* and forestall the next idle-blink for a while */
- }
- }
- HSetState((Handle)listH,listHState);
- }
-
- short GetControlNumber(register easyControl ech)
- /*
- * return the position in whatever list owns this control
- */
- {
- short n;
-
- n = 1;
- while( (**ech).prev)
- {
- n++;
- ech = (**ech).prev;
- }
- return n;
- }
-
-
- void UnhighlightSelection(easyControlList listH)
- /*
- * if there's a selected control,
- * put it in the unhighlighted phase
- */
- {
- register easyControl ech;
- register easyControlPtr ec;
- easyControlListPtr list;
- short listHState;
-
- listHState = HGetState((Handle)listH);
- HLock((Handle)listH);
- list = *listH;
-
- ech = list->selectedControl;
- if(ech)
- {
- list->nextIdle = TickCount()+list->ticksPerIdle; /* reset the idling phase to normal */
- HLock((Handle)ech);
- ec = *ech;
- list->idleRef = 0;
- SetPort((*ec->list)->ownerWindow);
- (*ec->type->idleProc)(ec,&list->idleRef);
- HUnlock((Handle)ech);
- }
- HSetState((Handle)listH,listHState);
- }
-
- easyControl ClickEasyControlList(easyControlList listH,Point p,
- controlClickResult *ccr,short mods)
- {
- register easyControl w;
- register easyControlPtr ec;
- easyControlListPtr list;
- short trackResult;
- short whichControl;
- short listHState;
-
- listHState = HGetState((Handle)listH);
- HLock((Handle)listH);
-
- list = *listH;
-
- w = list->firstControl;
- whichControl = 0;
-
- if(ccr)
- {
- ccr->whichControl = nil;
- ccr->tracked = false;
- ccr->value = 0;
- ccr->refcon = 0;
- ccr->id = 0;
- }
-
- while(w)
- {
- whichControl++;
- if(PtInRect(p,&(**w).rect) && (**w).type->trackProc) /* in rect and mouse sensitive */
- {
- SelectEasyControl(nil,listH);
- HLock((Handle)w);
- ec = *w;
- ec->flags |= easyControlTracking;
- if(ec->type->keyProc) /* never select keyless control */
- list->nextSelectedControl = w;
- trackResult = 0;
- ec->flags |= easyControlSetValue;
- (*ec->type->trackProc)(ec,p,&trackResult,mods);
- if(trackResult && ec->valueProc)
- (*ec->valueProc)(w);
- ec->flags &= ~easyControlSetValue;
-
- if(ccr)
- {
- ccr->whichControl = w;
- ccr->tracked = true;
- ccr->value = ec->value;
- ccr->refcon = ec->refcon;
- ccr->id = ec->id;
- }
-
- ec->flags &= ~easyControlTracking;
- (*ec->type->drawValueProc)(ec);
- HUnlock((Handle)w);
- goto goHome;
- }
- else
- w = (**w).next;
- }
- goHome:;
- HSetState((Handle)listH,listHState);
- return w;
- }
-
- void DrawEasyControlList(register easyControlList list)
- {
- WalkDrawEasyControlList(list,~0,0);
- }
-
- void DeactivateEasyControlList(easyControlList list)
- /*
- * A window should call this when it
- * becomes un-frontmost
- */
- {
- WalkDrawEasyControlList(list,~0,easyControlBack);
- }
-
- void ActivateEasyControlList(easyControlList list)
- /*
- * A window should call this when it
- * becomes frontmost
- */
- {
- WalkInvalEasyControlList(list,~easyControlBack,0);
- }
-
-
- void WalkDrawEasyControlList(easyControlList listH,long and,long or)
- /*
- * The gut routine of Draw, Activate, and DeactivateEasyControlList
- */
- {
- register easyControlPtr ec;
- register easyControl w;
- register easyControlListPtr list;
- short listHState;
- GrafPtr oldPort;
-
- if(!listH)
- goto goHome;
-
- GetPort(&oldPort);
-
- listHState = HGetState((Handle)listH);
- HLock((Handle)listH);
-
- list = *listH;
-
- SetPort(list->ownerWindow);
- TextFont(list->textFont);
- TextFace(list->textFace);
- TextSize(list->textSize);
- w = list->firstControl;
- while (w)
- {
- HLock((Handle)w);
- ec = *w;
- ec->flags &= and;
- ec->flags |= or;
- (*ec->type->drawProc)(ec);
- ValidRect(&ec->rect);
- HUnlock((Handle)w);
- w = ec->next;
- }
- HSetState((Handle)listH,listHState);
-
- SetPort(oldPort);
- goHome:;
- }
-
-
- void WalkInvalEasyControlList(easyControlList listH,long and,long or)
- /*
- * The gut routine of Draw, Activate, and DeactivateEasyControlList
- */
- {
- register easyControlPtr ec;
- register easyControl w;
- register easyControlListPtr list;
- short listHState;
-
- listHState = HGetState((Handle)listH);
- HLock((Handle)listH);
-
- list = *listH;
-
- SetPort(list->ownerWindow);
- w = list->firstControl;
- while (w)
- {
- HLock((Handle)w);
- ec = *w;
- ec->flags &= and;
- ec->flags |= or;
- InvalRect(&ec->rect);
- HUnlock((Handle)w);
- w = ec->next;
- }
- HSetState((Handle)listH,listHState);
- }
-
-
-
- void IdleEasyControlList(register easyControlList listH)
- {
- register easyControl ech;
- easyControlPtr ec;
- register easyControlListPtr list;
- long t;
- short listHState;
-
- listHState = HGetState((Handle)listH);
- HLock((Handle)listH);
- list = *listH;
-
- ech = list->selectedControl;
- if(ech)
- {
- t = TickCount();
- if(t > list->nextIdle)
- {
- list->nextIdle = t+list->ticksPerIdle;
- list->idleRef++;
- HLock((Handle)ech);
- ec = *ech;
- SetPort((*ec->list)->ownerWindow);
- (*ec->type->idleProc)(ec,&list->idleRef);
- HUnlock((Handle)ech);
- }
- }
- HSetState((Handle)listH,listHState);
- }
-
- void SetEasyControlValue(register easyControl ech,long v)
- {
- register easyControlPtr ec;
- becSetValueProcPtr svp;
-
- HLock((Handle)ech);
- ec = *ech;
- SetPort((*ec->list)->ownerWindow);
- svp = ec->type->setValueProc;
- if(svp)
- (*svp)(ec,v);
- else
- ec->value = v;
- ec->flags |= easyControlSetValue;
- (*ec->type->drawValueProc)(ec);
- ec->flags &= ~easyControlSetValue;
- HUnlock((Handle)ech);
- }
-
- long GetEasyControlValue(easyControl ech)
- {
- return (**ech).value;
- }
-
- long GetEasyControlRefcon(easyControl ech)
- {
- return (**ech).refcon;
- }
-
- long GetEasyControlID(easyControl ech)
- {
- return (**ech).id;
- }
-
-
-
- void SetEasyControlRange(easyControl ech,long l,long h)
- {
- register easyControlPtr ec;
-
- ec = *ech;
- ec->low = l;
- ec->high = h;
- }
-
- void SetEasyControlValueProc(easyControl ech,becValueProcPtr proc)
- {
- register easyControlPtr ec;
-
- ec = *ech;
- ec->valueProc = proc;
- }
-
- void SetEasyControlActionProc(easyControl ech,becActionProcPtr proc)
- {
- register easyControlPtr ec;
-
- ec = *ech;
- ec->actionProc = proc;
- }
-
- void SetEasyControlInitActionProc(easyControl ech,becInitActionProcPtr proc)
- {
- register easyControlPtr ec;
-
- ec = *ech;
- ec->initActionProc = proc;
- }
-
- void SetEasyControlDoneActionProc(easyControl ech,becDoneActionProcPtr proc)
- {
- register easyControlPtr ec;
-
- ec = *ech;
- ec->doneActionProc = proc;
- }
-
- void GetEasyControlColors(easyControl ech,register short *colors)
- {
- register short i;
- register short *src;
-
- if(ech)
- src = &(**ech).color[0];
- else
- src = &defaultColors[0];
- for(i = 5; i>=0; i--)
- *colors++ = *src++;
- }
-
- void SetEasyControlColors(easyControl ech,register short *colors)
- {
- register short i;
- register short *dst;
-
- if(ech)
- dst = &(**ech).color[0];
- else
- dst = &defaultColors[0];
- for(i = 5; i>=0; i--)
- *dst++ = *colors++;
- }
-
-
- void SelectEasyControl(easyControl ech,easyControlList listH)
- /*
- * Unselect the current one (if any)
- * and start the new one blinking.
- */
- {
- register easyControlListPtr list;
- short listHState;
-
- listHState = HGetState((Handle)listH);
- HLock((Handle)listH);
- list = *listH;
-
- list->idleRef = 0;
- UnhighlightSelection(listH);
- list->selectedControl = ech;
- list->nextIdle = 0;
- IdleEasyControlList(listH);
-
- HSetState((Handle)listH,listHState);
- }
-
- void GetEasyControlRect(easyControl ech,Rect *r)
- /*
- * Return the current bounds of the control
- */
- {
- *r = (**ech).rect;
- }
-
- void SetEasyControlRect(easyControl ech,Rect *r)
- /*
- * Move the control to the newly specified rectangle
- */
- {
- register easyControlPtr ec;
-
- HLock((Handle)ech);
- ec = *ech;
- SetPort((*ec->list)->ownerWindow);
- InvalRect(&ec->rect);
- ec->rect = *r;
- ec->flags |= easyControlMoved;
- InvalRect(&ec->rect);
- HUnlock((Handle)ech);
- }
-
- unsigned short Replicate555(register unsigned short x)
- {
- x &= 0x001F;
- return (x<<11) | (x<<6) | (x<<1) | (x>>4);
- }
-
- void Color555(register short x,register RGBColor *c)
- {
- c->red = Replicate555(x>>10);
- c->green = Replicate555(x>>5);
- c->blue = Replicate555(x);
- }
-
- void Fore555(register short x)
- {
- RGBColor c;
-
- Color555(x,&c);
- RGBForeColor(&c);
- RGBBackColor(&c);
- }
-
- #define kGrade 24000
- static long PinAdd(long,long);
- static long PinAdd(register long a,register long b)
- {
- a+= b;
- if(a > 65535)
- a = 65535;
- else if(a < 0)
- a = 0;
- return a;
- }
-
- void Fore555Light(register short x)
- {
- RGBColor c;
-
- Color555(x,&c);
- c.red = PinAdd(c.red,kGrade);
- c.green = PinAdd(c.green,kGrade);
- c.blue = PinAdd(c.blue,kGrade);
- /*
- c.green = (c.green + 65535L)>>1;
- c.blue = (c.blue + 65535L)>>1;*/
- RGBForeColor(&c);
- }
-
- void Fore555Dark(register short x)
- {
- RGBColor c;
-
- Color555(x,&c);
- c.red = PinAdd(c.red,-kGrade);
- c.green = PinAdd(c.green,-kGrade);
- c.blue = PinAdd(c.blue,-kGrade);
- /* c.red = c.red >> 1;
- c.green = c.green >> 1;
- c.blue = c.blue >> 1;*/
- RGBForeColor(&c);
- }
-
- #define kCCEdge 10000
- void Fore555Contrast(register short x)
- /*
- * Make a color that contrasts well with
- * the passed color: invert if close to a
- * side of the color cube, or shift by 32768
- */
- {
- RGBColor c;
-
- Color555(x,&c);
- if(c.red < kCCEdge || c.red > (65535-kCCEdge) ||
- c.green < kCCEdge || c.green > (65535-kCCEdge) ||
- c.blue < kCCEdge || c.blue > (65535-kCCEdge) )
- {
- c.red = ~c.red;
- c.green = ~c.green;
- c.blue = ~c.blue;
- }
- else
- {
- c.red += 32768;
- c.green += 32768;
- c.blue += 32768;
- }
- RGBForeColor(&c);
- }
-
- void RaisedRect(register Rect *r,register short x)
- /*
- * Draw rectangle r with a 1 pixel highlight
- * to raise it off the screen
- */
- {
- Fore555(x);
- if( ((r->right - r->left) <= 2) || ((r->bottom - r->top) <= 2) )
- PaintRect(r);
- else
- {
- PenSize(1,1);
- PaintRect(r);
- Fore555Light(x);
- MoveTo(r->left,r->bottom-1);
- LineTo(r->left,r->top);
- LineTo(r->right-1,r->top);
- Fore555Dark(x);
- LineTo(r->right-1,r->bottom-1);
- LineTo(r->left,r->bottom-1);
- }
- }
-
- void LoweredRect(Rect *r,register short x)
- /*
- * Draw rectangle r with a 1 pixel highlight
- * to raise it off the screen
- */
- {
- PenSize(1,1);
- Fore555(x);
- PaintRect(r);
- Fore555Dark(x);
- MoveTo(r->left,r->bottom-1);
- LineTo(r->left,r->top);
- LineTo(r->right-1,r->top);
- Fore555Light(x);
- LineTo(r->right-1,r->bottom-1);
- LineTo(r->left,r->bottom-1);
- }
-